package com.xuecheng.content.service.impl;

import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.segments.MergeSegments;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.xuecheng.base.exception.XueChengPlusException;
import com.xuecheng.content.mapper.CourseBaseMapper;
import com.xuecheng.content.mapper.TeachPlanMapper;
import com.xuecheng.content.mapper.TeachplanMediaMapper;
import com.xuecheng.content.model.dto.BindTeachPlanMediaDto;
import com.xuecheng.content.model.dto.SaveTeachPlanDto;
import com.xuecheng.content.model.dto.TeachPlanDto;
import com.xuecheng.content.model.po.CourseBase;
import com.xuecheng.content.model.po.TeachPlan;
import com.xuecheng.content.model.po.TeachPlanMedia;
import com.xuecheng.content.service.TeachPlanService;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.Collections;
import java.util.List;

/**
 * Created with IntelliJ IDEA.
 * Description: 课程计划相关
 * User: ws
 * Date: 2024-06-12
 * Time: 20:04
 */
@Service
public class TeachPlanServiceImpl implements TeachPlanService {
    @Resource
    private TeachPlanMapper teachPlanMapper;

    @Resource
    private CourseBaseMapper courseBaseMapper;

    @Resource
    private TeachplanMediaMapper teachplanMediaMapper;





    @Override
    public List<TeachPlanDto> findTeachPlanTree(Long courseId) {
        List<TeachPlanDto> teachPlanDtos = teachPlanMapper.selectTreeNodes(courseId);

        return teachPlanDtos;
    }

    @Transactional
    @Override
    public void saveTeachPlan(SaveTeachPlanDto saveTeachPlanDto) {
        // 通过课程计划的 id 判断是新增还是修改
        Long teachPlanId = saveTeachPlanDto.getId();
        if (teachPlanId == null) {
            // 新增
            TeachPlan teachPlanNew = new TeachPlan();
            // 拷贝属性
            BeanUtils.copyProperties(saveTeachPlanDto, teachPlanNew);
            // 设置排序字段，找到它的同级节点的最大值，加一即可
            LambdaQueryWrapper<TeachPlan> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(TeachPlan::getParentid, saveTeachPlanDto.getParentid());
            queryWrapper.orderByDesc(TeachPlan::getOrderby);
            queryWrapper.last("limit 1");
            TeachPlan teachPlan = teachPlanMapper.selectOne(queryWrapper);
            teachPlanNew.setOrderby(teachPlan == null ? 1 : teachPlan.getOrderby() + 1);
            teachPlanNew.setCreateDate(LocalDateTime.now());
            // 添加到数据库
            teachPlanMapper.insert(teachPlanNew);
        } else {
            // 修改
            TeachPlan teachPlan = teachPlanMapper.selectById(teachPlanId);
            // 拷贝属性
            BeanUtils.copyProperties(saveTeachPlanDto, teachPlan);
            teachPlan.setId(teachPlanId);
            teachPlan.setChangeDate(LocalDateTime.now());
            teachPlanMapper.updateById(teachPlan);
        }

    }

    @Override
    @Transactional
    public void removeTeachPlan(Long id) {
        TeachPlan teachPlan = teachPlanMapper.selectById(id);
        if (teachPlan == null) {
            XueChengPlusException.cast("课程计划不存在");
        }
        CourseBase courseBase = courseBaseMapper.selectById(teachPlan.getCourseId());
        if (courseBase == null) {
            XueChengPlusException.cast("课程不存在");
        }
        // 校验课程的状态，只有课程处于未发布状态（202002）时方可删除。
        // [{"code":"202001","desc":"审核未通过"},
        // {"code":"202002","desc":"未提交"},
        // {"code":"202003","desc":"已提交"},
        // {"code":"202004","desc":"审核通过"}]
//        String auditStatus = courseBase.getAuditStatus();
//        if (!"202002".equals(auditStatus)) {
//            XueChengPlusException.cast("删除失败，课程审核状态是未提交时方可删除。");
//        }


        Integer grade = teachPlan.getGrade();
        //删除第一级别的大章节时要求大章节下边没有小章节时方可删除。
        if (grade == 1) {
            LambdaQueryWrapper<TeachPlan> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(TeachPlan::getParentid, id);
            Integer count = teachPlanMapper.selectCount(queryWrapper);
            if (count > 0) {
                XueChengPlusException.cast("该课程计划下有子级计划，无法删除");
            }
        }
        // 删除课程计划
        teachPlanMapper.deleteById(id);
        // 删除第二级别的小章节的同时需要将teachplan_media表关联的信息也删除。
        // 即是大章节没有对应的 teachplan_media，sql 也不会出错，最多就是查询不到啥都不干
        teachplanMediaMapper.delete(Wrappers.<TeachPlanMedia>lambdaQuery().eq(TeachPlanMedia::getTeachplanId, id));
    }


    @Override
    public void moveTeachPlan(Long teachPlanId, String moveType) {
        TeachPlan teachPlan = teachPlanMapper.selectById(teachPlanId);
        if (teachPlan == null) {
            XueChengPlusException.cast("课程计划不存在");
        }
        // 查询和它同级别的菜单
        LambdaQueryWrapper<TeachPlan> queryWrapper = new LambdaQueryWrapper<>();
        // 同一级的课程计划下的同级别菜单
        queryWrapper.eq(TeachPlan::getCourseId, teachPlan.getCourseId());
        queryWrapper.eq(TeachPlan::getParentid, teachPlan.getParentid());
        queryWrapper.orderByAsc(TeachPlan::getOrderby);
        List<TeachPlan> teachPlans = teachPlanMapper.selectList(queryWrapper);
        // 只有一个不用排序
        if (CollectionUtils.isEmpty(teachPlans) || teachPlans.size() == 1) {
            return;
        }
        int size = teachPlans.size();
        // 根据传入的类型进行排序
        if ("moveup".equals(moveType)) {
            int index1 = teachPlans.indexOf(teachPlan);
            if (index1 == 0) {
                return;
            }
            int index2 = index1 - 1;
            Integer tmp = teachPlans.get(index1).getOrderby();
            teachPlan.setOrderby(teachPlans.get(index2).getOrderby());
            TeachPlan teachPlan2 = teachPlans.get(index2);
            teachPlan2.setOrderby(tmp);
            teachPlanMapper.updateById(teachPlan);
            teachPlanMapper.updateById(teachPlan2);
        } else if ("movedown".equals(moveType)) {
            int index1 = teachPlans.indexOf(teachPlan);
            if (index1 == size - 1) {
                return;
            }
            int index2 = index1 + 1;
            Integer tmp = teachPlans.get(index1).getOrderby();
            teachPlan.setOrderby(teachPlans.get(index2).getOrderby());
            TeachPlan teachPlan2 = teachPlans.get(index2);
            teachPlan2.setOrderby(tmp);
            teachPlanMapper.updateById(teachPlan);
            teachPlanMapper.updateById(teachPlan2);
        } else {
            XueChengPlusException.cast("移动类型错误");
        }
    }


    @Transactional
    @Override
    public TeachPlanMedia associationMedia(BindTeachPlanMediaDto bindTeachplanMediaDto) {
        //教学计划id
        Long teachplanId = bindTeachplanMediaDto.getTeachplanId();
        TeachPlan teachplan = teachPlanMapper.selectById(teachplanId);
        if (teachplan == null) {
            XueChengPlusException.cast("教学计划不存在");
        }
        Integer grade = teachplan.getGrade();
        if (grade != 2) {
            XueChengPlusException.cast("只允许第二级教学计划绑定媒资文件");
        }
        //课程id
        Long courseId = teachplan.getCourseId();

        //先删除原来该教学计划绑定的媒资
        teachplanMediaMapper.delete(new LambdaQueryWrapper<TeachPlanMedia>().eq(TeachPlanMedia::getTeachplanId, teachplanId));

        //再添加教学计划与媒资的绑定关系
        TeachPlanMedia teachplanMedia = new TeachPlanMedia();
        teachplanMedia.setCourseId(courseId);
        teachplanMedia.setTeachplanId(teachplanId);
        teachplanMedia.setMediaFileName(bindTeachplanMediaDto.getFileName());
        teachplanMedia.setMediaId(bindTeachplanMediaDto.getMediaId());
        teachplanMedia.setCreateDate(LocalDateTime.now());
        teachplanMediaMapper.insert(teachplanMedia);
        return teachplanMedia;
    }



    @Transactional
    @Override
    public void unbindMedia(Long teachPlanId, String mediaId) {
        // 教学计划id
        TeachPlan teachplan = teachPlanMapper.selectById(teachPlanId);
        if (teachplan == null) {
            XueChengPlusException.cast("教学计划不存在");
        }
        // 删除原来该教学计划绑定的媒资
        teachplanMediaMapper.delete(new LambdaQueryWrapper<TeachPlanMedia>().
                eq(TeachPlanMedia::getTeachplanId, teachPlanId).
                eq(TeachPlanMedia::getMediaId, mediaId));
    }
}
